package com.yiligi.myserver.controller;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.crypto.SecureUtil;
import com.yiligi.myserver.common.ResStatus;
import com.yiligi.myserver.common.ResultVO;
import com.yiligi.myserver.pojo.Files;
import com.yiligi.myserver.service.FileService;
import org.apache.catalina.connector.Response;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.IOException;
import java.net.URLEncoder;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@CrossOrigin
@RestController
public class FileController {

    @Value("${file.upload.path}")
    private String fileUploadPath;

    @Autowired
    private FileService fileService;

    @GetMapping("/file/selectFilePage")
    public ResultVO selectFilePage(
            @RequestParam int pageNum,
            @RequestParam int pageSize,
            @RequestParam String name,
            @RequestParam String type
    ) {
        pageNum = (pageNum-1) * pageSize;
        List<Files> files = fileService.selectFilePage(pageNum,pageSize,name,type);
        int total = fileService.selectFileCount(name,type);
        Map<String,Object> res = new HashMap<>();
        res.put("total",total);
        res.put("data",files);
        return new ResultVO(ResStatus.OK,"查询成功",res);
    }

    @DeleteMapping("/file/delete/{id}")
    public ResultVO deleteFile(@PathVariable("id")int id){
        if (fileService.deleteFile(id)==1){
            return new ResultVO(ResStatus.OK,"删除成功",null);
        }
        return new ResultVO(ResStatus.NO,"删除失败",null);
    }

    @PostMapping("/file/delete")
    public ResultVO deleteBatchFile(@RequestBody List<Integer> ids){
        if (fileService.delBatchFile(ids)){
            return new ResultVO(ResStatus.OK,"批量删除成功",null);
        }
        return new ResultVO(ResStatus.NO,"批量删除失败",null);
    }

    @PostMapping("/file/upload")
    public String upload(@RequestParam MultipartFile file) throws IOException {
        String originalFilename = file.getOriginalFilename();
        String type = FileUtil.extName(originalFilename);
        long size = file.getSize();

        // 定义一个文件唯一的标识码
        String uuid = IdUtil.fastSimpleUUID();
        String fileUUID = uuid + StrUtil.DOT + type;

        File uploadFile = new File(fileUploadPath + fileUUID);
        // 判断配置的文件目录是否存在，若不存在则创建一个新的文件目录
        File parentFile = uploadFile.getParentFile();
        if(!parentFile.exists()) {
            parentFile.mkdirs();
        }

        String url;
        // 获取文件的md5
        String md5 = SecureUtil.md5(file.getInputStream());
        // 从数据库查询是否存在相同的记录
        Files dbFiles = getFileByMd5(md5);
        if (dbFiles != null) { // 文件已存在
            url = dbFiles.getUrl();
        } else {
            // 上传文件到磁盘
            file.transferTo(uploadFile);
            // 数据库若不存在重复文件，则不删除刚才上传的文件
            url = "http://localhost:8081/file/" + fileUUID;
        }

        // 存储数据库
        Files saveFile = new Files();
        saveFile.setName(originalFilename);
        saveFile.setType(type);
        saveFile.setSize(size/1024);
        saveFile.setUrl(url);
        saveFile.setMd5(md5);
        saveFile.setIs_delete(false);
        saveFile.setEnable(true);
        fileService.uploadFile(saveFile);

        return url;
    }

    private Files getFileByMd5(String md5) {
        // 查询文件的md5是否存在
        List<Files> filesList = fileService.getFileMd5(md5);
        return filesList.size() == 0 ? null : filesList.get(0);
    }

    @GetMapping("/file/download/{fileUUID}")
    public void download(@PathVariable("fileUUID") String fileUUID, HttpServletResponse response) throws IOException {
        // 根据文件的唯一标识码获取文件
        File uploadFile = new File(fileUploadPath + fileUUID);
        // 设置输出流的格式
        ServletOutputStream os = response.getOutputStream();
        response.addHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileUUID, "UTF-8"));
        response.setContentType("application/octet-stream");
        // 读取文件的字节流
        os.write(FileUtil.readBytes(uploadFile));
        os.flush();
        os.close();
    }

    @GetMapping("/file/{avatar_url}")
    public void getUrl(@PathVariable("avatar_url")String avatar_url,HttpServletResponse response) throws IOException {
        File uploadFile = new File(fileUploadPath + avatar_url);
        // 设置输出流的格式
        ServletOutputStream os = response.getOutputStream();
        response.addHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(avatar_url, "UTF-8"));
        response.setContentType("application/octet-stream");
        // 读取文件的字节流
        os.write(FileUtil.readBytes(uploadFile));
        os.flush();
        os.close();
    }

}
